home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Amiga Plus Special 23
/
AMIGAplus Sonderheft 23 (2000)(Falke)(DE)[!].iso
/
Updates
/
Datatypes
/
RGFX-DT35
/
Source
/
dispatcher.c
< prev
next >
Wrap
C/C++ Source or Header
|
1999-11-14
|
15KB
|
648 lines
#include <clib/alib_protos.h>
#include <pragma/datatypes_lib.h>
#include <pragma/dos_lib.h>
#include <pragma/exec_lib.h>
#include <pragma/graphics_lib.h>
#include <pragma/iffparse_lib.h>
#include <pragma/intuition_lib.h>
#include <pragma/utility_lib.h>
#include <pragma/xpkmaster_lib.h>
#include <datatypes/pictureclass.h>
#include <exec/memory.h>
#include <intuition/icclass.h>
#include <string.h>
#include "class.h"
#include "rgfx.h"
struct Arg1
{
char *xpk;
long *xpkmode;
char *password;
};
ULONG SaveRGFX(IClass *cl,Object *obj,dtWrite *msg);
static long iff2dos[]=
{
0,
0,
DTERROR_INVALID_DATA,
ERROR_NO_FREE_STORE,
ERROR_SEEK_ERROR,
ERROR_SEEK_ERROR,
ERROR_SEEK_ERROR,
DTERROR_INVALID_DATA,
DTERROR_INVALID_DATA,
ERROR_OBJECT_WRONG_TYPE,
ERROR_REQUIRED_ARG_MISSING,
0xDEADDEAD
};
static long chunks[]=
{
ID_RGFX,ID_RGHD,
ID_RGFX,ID_RSCM,
ID_RGFX,ID_RCOL,
ID_RGFX,ID_NAME,
ID_RGFX,ID_AUTH,
ID_RGFX,ID_ANNO,
ID_RGFX,ID_Copyright,
ID_RGFX,ID_FVER
};
void ReadPrefs(Data *data)
{
char *var;
strcpy(data->xpk,"NUKE");
data->xpkmode=100;
if(data->password)
{
FreeVec(data->password);
data->password=0;
}
if(var=(char *)AllocVec(256,0))
{
if(GetVar("ENV:DataTypes/rgfx.prefs",var,256,LV_VAR|GVF_GLOBAL_ONLY)>=0)
{
RDArgs *rdargs;
if(rdargs=(RDArgs *)AllocDosObject(DOS_RDARGS,0))
{
RDArgs *args;
Arg1 para;
rdargs->RDA_Source.CS_Buffer=var;
rdargs->RDA_Source.CS_Length=strlen(var);
rdargs->RDA_Source.CS_CurChr=0;
memset(¶,0,sizeof(Arg1));
if(args=ReadArgs("XPK/A,XPKMODE/A/N,PASSWORD",(long *)¶,rdargs))
{
strncpy(data->xpk,para.xpk,4);
data->xpk[4]=0;
data->xpkmode=*para.xpkmode;
if(data->xpkmode<0) data->xpkmode=0;
else if(data->xpkmode>100) data->xpkmode=100;
if(para.password)
{
if(data->password=(char *)AllocVec(strlen(para.password)+1,MEMF_CLEAR)) strcpy(data->password,para.password);
}
FreeArgs(args);
}
FreeDosObject(DOS_RDARGS,rdargs);
}
}
FreeVec(var);
}
}
ULONG Colors2DT(Object *obj,UBYTE *color)
{
UBYTE *cr;
ULONG *cregs,i,num,error=0;
GetDTAttrs(obj,PDTA_NumColors,&num,PDTA_ColorRegisters,&cr,PDTA_CRegs,&cregs,TAG_END);
if(cr&&cregs)
{
for(i=0;i<num;i++,cr+=3,cregs+=3,color+=4)
{
cr[0]=color[1];
cr[1]=color[2];
cr[2]=color[3];
cregs[0]=cr[0]<<24;
cregs[1]=cr[1]<<24;
cregs[2]=cr[2]<<24;
}
}
else error=ERROR_NO_FREE_STORE;
return error;
}
static void GetRGHD(Object *obj,RGHD *rh,BitMapHeader *bh,Data *data)
{
bh->bmh_Left=rh->rgfx_LeftEdge;
bh->bmh_Top=rh->rgfx_TopEdge;
bh->bmh_Width=rh->rgfx_Width;
bh->bmh_Height=rh->rgfx_Height;
bh->bmh_PageWidth=rh->rgfx_PageWidth?rh->rgfx_PageWidth:bh->bmh_Width;
bh->bmh_PageHeight=rh->rgfx_PageHeight?rh->rgfx_PageHeight:bh->bmh_Height;
bh->bmh_Depth=rh->rgfx_Depth;
bh->bmh_Compression=cmpByteRun1;
bh->bmh_XAspect=rh->rgfx_XAspect;
bh->bmh_YAspect=rh->rgfx_YAspect;
}
static ULONG GetRSCM(Object *obj,IFFHandle *iff,BitMapHeader *bh,Data *data,ULONG rgfxdepth)
{
ULONG mode=0,numc=0;
StoredProperty *sp;
mode=INVALID_ID;
if(sp=FindProp(iff,ID_RGFX,ID_RSCM))
{
RSCM *rscm=(RSCM *)sp->sp_Data;
if(!ModeNotAvailable(rscm->rscm_AGA))
{
ULONG dipf=0;
if(rscm->rscm_AGA&HAM_KEY)
{
numc=(bh->bmh_Depth==8)?64:16;
dipf=DIPF_IS_HAM;
}
else if(rscm->rscm_AGA&EXTRAHALFBRITE_KEY)
{
numc=32;
dipf=DIPF_IS_EXTRAHALFBRITE;
}
if(dipf) mode=BestModeID(
BIDTAG_NominalWidth,bh->bmh_PageWidth,BIDTAG_NominalHeight,bh->bmh_PageHeight,
BIDTAG_DesiredWidth,bh->bmh_Width,BIDTAG_DesiredHeight,bh->bmh_Height,BIDTAG_Depth,bh->bmh_Depth,
BIDTAG_DIPFMustHave,dipf,BIDTAG_DIPFMustNotHave,DIPF_IS_DUALPF|DIPF_IS_PF2PRI,TAG_END);
}
}
if(mode==INVALID_ID)
{
mode=BestModeID(
BIDTAG_NominalWidth,bh->bmh_PageWidth,BIDTAG_NominalHeight,bh->bmh_PageHeight,
BIDTAG_DesiredWidth,bh->bmh_Width,BIDTAG_DesiredHeight,bh->bmh_Height,
BIDTAG_Depth,bh->bmh_Depth,
BIDTAG_DIPFMustNotHave,DIPF_IS_DUALPF|DIPF_IS_PF2PRI|DIPF_IS_HAM|DIPF_IS_EXTRAHALFBRITE,TAG_END);
numc=1<<bh->bmh_Depth;
}
if(mode!=INVALID_ID)
{
SetDTAttrs(obj,0,0,PDTA_ModeID,mode,TAG_END);
if(numc) SetDTAttrs(obj,0,0,PDTA_NumColors,numc,TAG_END);
}
return mode;
}
static ULONG GetRCOL(Object *obj,IFFHandle *iff,RGHD *rh)
{
ULONG error=0;
if(rh->rgfx_Depth<=8)
{
StoredProperty *sp;
if(sp=FindProp(iff,ID_RGFX,ID_RCOL))
{
RCOL *rcol=(RCOL *)sp->sp_Data;
ULONG n,*cregs;
UBYTE *cr,*p;
GetDTAttrs(obj,PDTA_NumColors,&n,PDTA_ColorRegisters,&cr,PDTA_CRegs,&cregs,TAG_END);
if(cr&&cregs)
{
ULONG i;
n*=3;
for(i=0,p=rcol->rcol_Colors[0];i<n;i++,p++,cr++,cregs++)
{
*cr=*p;
*cregs=(*p)<<24;
}
}
else error=ERROR_NO_FREE_STORE;
}
else error=ERROR_REQUIRED_ARG_MISSING;
}
return error;
}
static ULONG GetBody_BP8(IFFHandle *iff,RGHD *rh,BitMap *bm,Data *data)
{
ULONG error=0,d;
for(d=0;d<rh->rgfx_Depth;d++)
{
ULONG y;
UBYTE *pl=bm->Planes[d];
for(y=0;y<rh->rgfx_Height;y++,pl+=bm->BytesPerRow)
{
long err;
if((err=ReadChunkBytes(iff,pl,rh->rgfx_BytesPerLine)<0))
{
error=iff2dos[-err];
break;
}
}
}
return error;
}
static ULONG GetBody_BC8(IFFHandle *iff,RGHD *rh,BitMap *bm,Data *data)
{
ULONG error=0;
long err;
UBYTE *pix;
RastPort rp;
if(pix=(UBYTE *)AllocVec(rh->rgfx_Width*rh->rgfx_Height,0))
{
if((err=ReadChunkBytes(iff,pix,rh->rgfx_Width*rh->rgfx_Height))<0) error=iff2dos[-err];
else
{
InitRastPort(&rp);
rp.BitMap=bm;
WriteChunkyPixels(&rp,0,0,rh->rgfx_Width-1,rh->rgfx_Height-1,pix,rh->rgfx_Width);
}
FreeVec(pix);
}
else
{
if(pix=(UBYTE *)AllocVec(rh->rgfx_Width,0))
{
ULONG y;
InitRastPort(&rp);
rp.BitMap=bm;
for(y=0;y<rh->rgfx_Height;y++)
{
long err;
if((err=ReadChunkBytes(iff,pix,rh->rgfx_Width))<0)
{
error=iff2dos[-err];
break;
}
WriteChunkyPixels(&rp,0,y,rh->rgfx_Width-1,1,pix,rh->rgfx_Width);
}
FreeVec(pix);
}
else error=ERROR_NO_FREE_STORE;
}
return error;
}
static ULONG GetBody_RGB_V43(Object *obj,IFFHandle *iff,RGHD *rh,Data *data)
{
ULONG error=0;
UBYTE *pix;
long err;
if(pix=(UBYTE *)AllocVec(rh->rgfx_BytesPerLine*rh->rgfx_Height,0))
{
if((err=ReadChunkBytes(iff,pix,rh->rgfx_BytesPerLine*rh->rgfx_Height))<0) error=iff2dos[-err];
else DoMethod(obj,PDTM_WRITEPIXELARRAY,pix,PBPAFMT_RGB,rh->rgfx_BytesPerLine,0,0,rh->rgfx_Width,rh->rgfx_Height);
FreeVec(pix);
}
else if(pix=(UBYTE *)AllocVec(rh->rgfx_BytesPerLine,0))
{
ULONG y;
for(y=0;y<rh->rgfx_Height;y++)
{
if((err=ReadChunkBytes(iff,pix,rh->rgfx_BytesPerLine))<0)
{
error=iff2dos[-err];
break;
}
DoMethod(obj,PDTM_WRITEPIXELARRAY,pix,PBPAFMT_RGB,rh->rgfx_BytesPerLine,0,y,rh->rgfx_Width,1);
}
FreeVec(pix);
}
else error=ERROR_NO_FREE_STORE;
return error;
}
static ULONG GetBody_XPKBP8(IFFHandle *iff,RGHD *rh,BitMap *bm,Data *data)
{
ULONG error=0,d,y;
XpkFib *fib;
UBYTE *mem,*pl;
if(!XpkUnpackTags(XPK_InFH,iff->iff_Stream,XPK_GetOutBuf,&mem,XPK_GetOutBufLen,&y,TAG_END))
{
UBYTE *p=mem;
for(d=0;d<rh->rgfx_Depth;d++)
{
pl=bm->Planes[d];
for(y=0;y<rh->rgfx_Height;y++,pl+=bm->BytesPerRow,p+=rh->rgfx_BytesPerLine) CopyMem(p,pl,bm->BytesPerRow);
}
FreeMem(mem,y);
}
else if(!XpkOpenTags(&fib,XPK_InFH,iff->iff_Stream,TAG_END))
{
if(mem=(UBYTE *)AllocVec(fib->xf_NLen,0))
{
long p=-1,clen=-1;
for(d=0;d<rh->rgfx_Depth;d++)
{
pl=bm->Planes[d];
for(y=0;y<rh->rgfx_Height;y++,pl+=bm->BytesPerRow)
{
ULONG x;
for(x=0;x<rh->rgfx_BytesPerLine;x++)
{
if(p>=clen)
{
if((clen=XpkRead(fib,mem,fib->xf_NLen))<0)
{
error=DTERROR_INVALID_DATA;
y=rh->rgfx_Height;
d=rh->rgfx_Depth;
break;
}
p=0;
}
pl[x]=mem[p];
p++;
}
}
}
FreeVec(mem);
}
else error=ERROR_NO_FREE_STORE;
XpkClose(fib);
}
else error=DTERROR_INVALID_DATA;
return error;
}
static ULONG GetBody_XPKBC8(IFFHandle *iff,RGHD *rh,BitMap *bm,Data *data)
{
ULONG error=0,pixlen;
UBYTE *pix;
RastPort rp;
if(!XpkUnpackTags(XPK_InFH,iff->iff_Stream,XPK_GetOutBuf,&pix,XPK_GetOutBufLen,&pixlen,TAG_END))
{
InitRastPort(&rp);
rp.BitMap=bm;
WriteChunkyPixels(&rp,0,0,rh->rgfx_Width-1,rh->rgfx_Height-1,pix,rh->rgfx_Width);
FreeMem(pix,pixlen);
}
else